package apple

import (
	"crypto/x509"
	"dta-apk/global"
	"dta-apk/utils"
	"encoding/pem"
	"log"
	"os"
	"path/filepath"

	"github.com/dgrijalva/jwt-go"
)

/*
函数名：生成请求统一header

参数：
- 参数headers: 自定义header
- 参数scopes: 需要授权的接口数组

返回值：
- 返回值1: 请求header
*/
func getHeader(headers map[string]string, scopes []string) map[string]string {
	auth := getAuthorization(scopes)
	if headers != nil {
		headers["Authorization"] = auth
		return headers
	}

	return map[string]string{"Authorization": auth}
}

// 获取授权字符串
func getAuthorization(scopes []string) string {
	tokenSign := createJwt(scopes)
	return "Bearer " + tokenSign
}

/*
函数名：创建接口请求的对用签名

参数：
- 参数scope: 需要授权的接口数组

返回值：
- 返回值1: 签名值
*/
func createJwt(scopes []string) string {
	// 构建 JWT 头部
	claims := jwt.MapClaims{
		"iss":   global.Config.App.Apple.IssuerId, // 认证令牌的发放者
		"iat":   utils.TimeStamp(),                // 令牌的创建时间
		"exp":   utils.ExpireStamp(2),             // 令牌的过期时间,
		"aud":   "appstoreconnect-v1",             // 固定值
		"scope": scopes,                           // 允许此令牌的操作列表,接口列表
	}
	// 生成token
	token := jwt.NewWithClaims(jwt.SigningMethodES256, claims)
	// 添加header
	token.Header["alg"] = "ES256"                       // 签名加密算法，固定算法
	token.Header["kid"] = global.Config.App.Apple.KeyId // 密钥id
	token.Header["type"] = "jwt"                        // 令牌类型，固定值

	// 密钥签名
	secret := getPrivateSecret()
	tokenString, err := token.SignedString(secret)
	if err != nil {
		log.Fatal(err)
	}
	return tokenString
}

// 与密钥ID关联的私钥
func getPrivateSecret() any {
	currentDir, err := os.Getwd()
	if err != nil {
		log.Fatal(err)
	}
	filePath := filepath.Join(currentDir, "apple", "AuthKey_3QVZ8M6827.p8")
	// 读取密钥文件
	privateKeyData, err := os.ReadFile(filePath)
	if err != nil {
		log.Fatal(err)
	}
	// 解析私钥数据
	block, _ := pem.Decode(privateKeyData)
	if block == nil || block.Type != "PRIVATE KEY" {
		log.Fatal("failed to decode PEM block containing private key")
	}

	// 解析私钥数据
	privateKey, err := x509.ParsePKCS8PrivateKey(block.Bytes)
	if err != nil {
		log.Fatal(err)
	}

	return privateKey
}

// 请求接口名称
func getUrl(api string) string {
	return domain_url + api
}
